from flask import Flask, request, jsonify, send_from_directory
import os
import hashlib
import json
from werkzeug.utils import secure_filename

app = Flask(__name__)

# 文件上传配置
UPLOAD_FOLDER = 'uploads'
ALLOWED_EXTENSIONS_VIDEO = {'mp4', 'avi', 'mov', 'webm'}  # 支持 WebM 格式
ALLOWED_EXTENSIONS_IMAGE = {'jpg', 'jpeg', 'png', 'gif'}

app.config['UPLOAD_FOLDER'] = UPLOAD_FOLDER

# 检查文件扩展名是否允许
def allowed_file(filename, allowed_extensions):
    return '.' in filename and filename.rsplit('.', 1)[1].lower() in allowed_extensions

# 计算文件的 MD5 值
def calculate_md5(file_path):
    hash_md5 = hashlib.md5()
    with open(file_path, "rb") as f:
        for chunk in iter(lambda: f.read(4096), b""):
            hash_md5.update(chunk)
    return hash_md5.hexdigest()

# 获取视频文件的宽度和高度（使用 OpenCV）
def get_video_dimensions(file_path):
    try:
        import cv2
        cap = cv2.VideoCapture(file_path)
        width = int(cap.get(cv2.CAP_PROP_FRAME_WIDTH))
        height = int(cap.get(cv2.CAP_PROP_FRAME_HEIGHT))
        cap.release()
        return width, height
    except Exception as e:
        print(f"Error reading video dimensions: {e}")
        return None, None

# 首页路由
@app.route('/')
def index():
    return send_from_directory('.', 'index.html')

# 文件上传路由
@app.route('/upload', methods=['POST'])
def upload_file():
    # 检查是否有视频文件
    if 'file' not in request.files:
        return jsonify({"error": "No video file part"}), 400

    video_file = request.files['file']
    if video_file.filename == '':
        return jsonify({"error": "No selected video file"}), 400

    # 检查视频文件格式
    if not allowed_file(video_file.filename, ALLOWED_EXTENSIONS_VIDEO):
        return jsonify({"error": "Video file type not allowed"}), 400

    # 保存视频文件
    video_filename = secure_filename(video_file.filename)
    video_path = os.path.join(app.config['UPLOAD_FOLDER'], video_filename)
    video_file.save(video_path)

    # 获取视频文件的宽度和高度
    width, height = get_video_dimensions(video_path)
    if width is None or height is None:
        return jsonify({"error": "Failed to read video dimensions"}), 400

    # 获取封面图片（可选）
    cover_filename = None
    if 'cover' in request.files:
        cover_file = request.files['cover']
        if cover_file.filename != '':
            if allowed_file(cover_file.filename, ALLOWED_EXTENSIONS_IMAGE):
                # 将封面图片命名为与视频文件同名，但扩展名不同
                video_basename = os.path.splitext(video_filename)[0]
                cover_extension = cover_file.filename.rsplit('.', 1)[1].lower()
                cover_filename = f"{video_basename}.{cover_extension}"
                cover_path = os.path.join(app.config['UPLOAD_FOLDER'], cover_filename)
                cover_file.save(cover_path)
            else:
                return jsonify({"error": "Cover image file type not allowed"}), 400

    # 获取表单数据
    video_name = request.form.get('name')
    description = request.form.get('description')
    category = request.form.get('category')
    author = request.form.get('author')

    # 计算视频文件的 MD5 值和大小
    file_size = os.path.getsize(video_path)
    file_md5 = calculate_md5(video_path)

    # 构建视频信息
    video_info = {
        "name": video_name,
        "description": description,
        "category": category,
        "author": author,
        "width": width,
        "height": height,
        "cover": cover_filename,  # 封面图片文件名
        "file_size": file_size,
        "md5": file_md5
    }

    # 保存视频信息到 JSON 文件
    json_filename = os.path.splitext(video_filename)[0] + '.json'
    json_path = os.path.join(app.config['UPLOAD_FOLDER'], json_filename)

    with open(json_path, 'w') as json_file:
        json.dump(video_info, json_file, indent=4)

    return jsonify({"message": "File uploaded successfully", "info": video_info}), 200

# 启动 Flask 应用
if __name__ == '__main__':
    if not os.path.exists(UPLOAD_FOLDER):
        os.makedirs(UPLOAD_FOLDER)
    app.run(debug=True)